import { Expand } from "@ct0/icons";
import classNames from "classnames";
import RcInputNumber from "rc-input-number";
import type { CSSProperties } from "react";
import React, { useContext } from "react";
import Select from "../../../Select";
import { ThemeContext } from "../../../theme";
import useStyles from "./styles";

interface Props<Value> {
  invalid?: boolean;
  value?: Value;
  maxLength?: number;
  placeholder?: string;
  prefix?: string;
  suffix?: string;
  disabled?: boolean;
  max?: number;
  min?: number;
  type?: "number" | "text" | "password";
  style?: CSSProperties;
  className?: string;
  unitValue?: string;
  units?: Array<{ label: string; value: string }>;
  onUnitChange?: (unit: string) => void;
  onChange: (v: Value) => void;
}

export default function StringInput<Value extends string | number>({
  invalid,
  value,
  unitValue,
  placeholder,
  min,
  max,
  prefix,
  suffix,
  type,
  className,
  disabled,
  units,
  onUnitChange,
  onChange,
}: Props<Value>) {
  const { fontSize } = useContext(ThemeContext);
  const classes = useStyles({ fontSize });

  const handler = (e: React.FormEvent<HTMLInputElement>) => {
    const v = (e.target as HTMLInputElement).value as Value;
    onChange(v);
  };

  return (
    <div
      className={classNames(
        classes.strinInput,
        invalid && classes.invalid,
        className
      )}
    >
      {prefix && (
        <div className={classNames(classes.prefixAndSubfix, classes.prefix)}>
          {prefix}
        </div>
      )}
      {type === "number" ? (
        <RcInputNumber
          prefixCls="ct0-input-number"
          disabled={disabled}
          max={max as Value}
          min={min as Value}
          value={value}
          placeholder={placeholder}
          onChange={(v) => {
            onChange(v as Value);
          }}
          upHandler={<Expand className="ct0-input-number-up-handler" />}
          downHandler={<Expand />}
        />
      ) : (
        <input
          disabled={disabled}
          type={type}
          className={classNames(classes.input, disabled && classes.disabled)}
          placeholder={placeholder}
          value={value}
          minLength={min}
          maxLength={max}
          onChange={handler}
        />
      )}
      {units && (
        <Select
          className={classes.units}
          value={unitValue}
          options={units}
          onChange={onUnitChange}
        />
      )}
      {suffix && (
        <div className={classNames(classes.prefixAndSubfix, classes.suffix)}>
          {suffix}
        </div>
      )}
    </div>
  );
}
